﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using MazeNet.Communication;
using System.Net;
using MazeNetKI;
using NichosNotSoRandomKi;

namespace MazeNetGUI
{
    public partial class FormMain : Form
    {
        MazeNetClient _mClient;
        MazeNetHandler _mHandler;

        public FormMain()
        {
            InitializeComponent();
        }

        private void btn_Connect_Click(object sender, EventArgs e)
        {
            string _lName;
            try
            {
                _mClient = new MazeNetClient(new System.Net.IPEndPoint(IPAddress.Parse(tb_IP.Text), int.Parse(tb_Port.Text)));

                _mClient.OnMessageReceived += HandleIncomingMessages;
                _mClient.OnMessageSent += HandleOutgoingMessages;

                //KI waehlen
                switch (cb_KI.SelectedIndex)
                {
                    case 0:
                        _mHandler = new MazeNetHandler(_mClient, new RandomKIPlayer());
                        _lName = "Random @ Gnocchi";
                        break;
                    case 1:
                        _mHandler = new MazeNetHandler(_mClient, new NotSoRandomKI());
                        _lName = "NotSoRandom @ Gnocchi";
                        break;
                    default:
                        MessageBox.Show("Keine KI gewaehlt");
                        return;
                }

                if (_mClient.Connect())
                {

                    _mClient.LogIn(_lName);
                }
                else
                {
                    MessageBox.Show("Verbindung zum Server konnte nicht aufgebaut werden");
                }
                gb_Connection.Enabled = false;
            }
            catch (Exception e1)
            {
                MessageBox.Show("Fehlerhafte IP oder Port");
            }
        }

        private void HandleIncomingMessages(object sender, MazeNetEventArgs e)
        {
            switch (e.MazeComMessage.mcType)
            {
                case MazeComType.AWAITMOVE:
                    //Board malen
                    if (boardPanel1.InvokeRequired)
                        boardPanel1.Invoke(new Action(() =>
                        {
                            boardPanel1.Board = ((AwaitMoveMessageType)e.MazeComMessage.Item).board;
                            nud_Rounds.Value++;
                        }));
                    else
                        boardPanel1.Board = ((AwaitMoveMessageType)e.MazeComMessage.Item).board;
                    //Karte malen
                    //if (cardPanel1.InvokeRequired)
                    //    cardPanel1.Invoke(new Action(() => { cardPanel1.Card = ((AwaitMoveMessageType)e.MazeComMessage.Item).board.shiftCard; }));
                    //else
                    //    cardPanel1.Card = ((AwaitMoveMessageType)e.MazeComMessage.Item).board.shiftCard;
                    break;
                case MazeComType.WIN:
                    MessageBox.Show(string.Format("Gewonnen hat: {0}", ((WinMessageType)e.MazeComMessage.Item).winner));
                    break;
            }
        }

        private void HandleOutgoingMessages(object sender, MazeNetEventArgs e)
        {
            switch (e.MazeComMessage.mcType)
            {
                case MazeComType.MOVE:
                    //Board erstellen
                    MoveMessageType _lMessage = (MoveMessageType)e.MazeComMessage.Item;
                    boardType _lBoard = new boardType(boardPanel1.Board);
                    _lBoard.Push(new Point(_lMessage.shiftPosition.col, _lMessage.shiftPosition.row), true);
                    _lBoard.MovePlayer(_mClient.Id, new Point(_lMessage.newPinPos.col, _lMessage.newPinPos.row));

                    //Board malen
                    if (boardPanel2.InvokeRequired)
                        boardPanel2.Invoke(new Action(() => { boardPanel2.Board = _lBoard; }));
                    else
                        boardPanel2.Board = ((AwaitMoveMessageType)e.MazeComMessage.Item).board;
                    break;
            }
        }
    }
}
